#include <iostream>

#include <cstring>
using namespace std;
class HugeInteger
{
    public:
        char * content;
        int  len;
        HugeInteger();
        HugeInteger(int a);
        HugeInteger(char * a);
        HugeInteger(const HugeInteger & a);
        ~ HugeInteger();
        void show();
        friend ostream & operator <<(ostream & os, const HugeInteger  a);
        HugeInteger operator+ (HugeInteger & a);
        HugeInteger operator+ (int a);
        HugeInteger operator+ (char * a);
        void operator= (const HugeInteger a);

};


HugeInteger::HugeInteger()
{
    len = 1;
    content = new char[2];
    content[0] = '0';
    content[1] = '\0';
}
HugeInteger::HugeInteger(int a)
{
    char s[32];
    sprintf(s,"%d",a);
    len = strlen(s);
    content = new char[len+1];
    strcpy(content,s);
}

HugeInteger::HugeInteger(char * a)
{
    len = strlen(a);
    content = new char[len + 1]; 
    strcpy(content,a);
}

HugeInteger::HugeInteger(const HugeInteger & a)
{
    this->len = a.len;
    this->content = new char[a.len+1];
    strcpy(this->content,a.content);
}

HugeInteger::~HugeInteger()
{
    delete [] content;
}
void HugeInteger::operator= (const HugeInteger a)
{
    delete this->content;
    this->len = a.len;
    this->content = new char[a.len+1];
    strcpy(this->content,a.content);
       
}
HugeInteger HugeInteger::operator+(HugeInteger & h)
{
    int slen = ((this->len > h.len) ? this->len : h.len);
    int  * a = new int[slen];
    int  * b = new int[slen];
    int  * c = new int[slen];
    for(int i = 0; i<slen; i++)
    {
        if(i<(slen-this->len))
             a[i] = 0;
        else
             a[i] = this->content[i-(slen-this->len)] - '0';
        if(i<(slen-h.len))
             b[i] = 0;
        else
             b[i] = h.content[i-(slen-h.len)] - '0';
    }
    int carry = 0;
    for(int i = slen-1; i>=0; i--)
    {
       int sum  = a[i] + b[i] + carry;
       c[i] = sum%10;
       carry = sum/10;
    }
    char * s = NULL;
    char * p = NULL;
    int newLen = 0;
    if(carry > 0){
        newLen = slen + 1;
        s = new char[slen + 1+1];
        s[0] = (char)(carry + '0');
        p = s+1;
    }
    else{
        newLen = slen;
        s = new char[slen + 1];
        p = s;
    }
    for(int i  = 0; i<slen; i++)
        *p++ =(char) (c[i]+'0');
    *p = '\0';    
    
    delete [] a;
    delete [] b;
    delete [] c;
    
    HugeInteger result(s);
    delete [] s;
    return result;
}
HugeInteger HugeInteger::operator+(int a)
{
    HugeInteger aa(a);
    HugeInteger b = (*this) + aa;
    return b;
}
HugeInteger HugeInteger::operator+( char * a)
{
    HugeInteger aa(a);
    HugeInteger b = (*this) + aa;
    return b;
}
ostream & operator << (ostream & os,const HugeInteger  a)
{
    os<<a.content; 
    return os;
}
int main()
{

   HugeInteger n1( 7654321 );
   HugeInteger n2( 7891234 );
   HugeInteger n3( "99999999999999999999999999999" );
   HugeInteger n4( "1" );
   HugeInteger n5;
   cout << "n1 is " << n1 << "\nn2 is " << n2
      << "\nn3 is " << n3 << "\nn4 is " << n4
      << "\nn5 is " << n5 << "\n\n";
   n5 = n1 + n2;
   cout << n1 << " + " << n2 << " = " << n5 << "\n\n";

   cout << n3 << " + " << n4 << "\n= " << ( n3 + n4 ) << "\n\n";

   n5 = n1 + 9;
   cout << n1 << " + " << 9 << " = " << n5 << "\n\n";
   n5 = n2 + "10000";
   cout << n2 << " + " << "10000" << " = " << n5 << endl;
    return 0;
}